<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<!--

/*
** Copyright (c) 2012 The Khronos Group Inc.
**
** Permission is hereby granted, free of charge, to any person obtaining a
** copy of this software and/or associated documentation files (the
** "Materials"), to deal in the Materials without restriction, including
** without limitation the rights to use, copy, modify, merge, publish,
** distribute, sublicense, and/or sell copies of the Materials, and to
** permit persons to whom the Materials are furnished to do so, subject to
** the following conditions:
**
** The above copyright notice and this permission notice shall be included
** in all copies or substantial portions of the Materials.
**
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
** EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
** MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
** IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
** CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
** TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
** MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
*/

-->

<link rel="stylesheet" type="text/css" href="../unit.css" />
<script type="application/x-javascript" src="../unit.js"></script>
<script type="application/x-javascript" src="../util.js"></script>
<script type="application/x-javascript">

Tests.autorun = false;
Tests.message = "This might take a second or two. Take the upload numbers with a dose of salt, as there's no drawing code using the data.";

Tests.startUnit = function () {
  var canvas = document.getElementById('gl');
  var gl = getGLContext(canvas);
  return [gl];
}

Tests.testTexImage2D = function(gl) {
    var tex = gl.createTexture();
    var texArr = new Array(256*256*4);
    var bufData = new Array(256*256*4);
    for (var i=0; i<texArr.length; i++) texArr[i] = 0;
    for (var i=0; i<bufData.length; i++) bufData[i] = 0.5;
    gl.bindTexture(gl.TEXTURE_2D, tex);
    time("texImage2D", function() {
        for (var i=0; i<100; i++)
            gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, 256, 256, 0, gl.RGBA, gl.UNSIGNED_BYTE, texArr);
    });
    time("texImage2D", function() {
        for (var i=0; i<100; i++)
            gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, 256, 256, 0, gl.RGBA, gl.UNSIGNED_BYTE, texArr);
    });
    time("texSubImage2D", function() {
        for (var i=0; i<100; i++)
            gl.texSubImage2D(gl.TEXTURE_2D, 0, 0, 0, 256, 256, gl.RGBA, gl.UNSIGNED_BYTE, texArr);
    });
    var img = document.getElementById('logo');
    time("texImage2DHTML", function() {
        for (var i=0; i<100; i++)
            gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, img);
    });
    time("texSubImage2DHTML", function() {
        for (var i=0; i<100; i++)
            gl.texSubImage2D(gl.TEXTURE_2D, 0, 0, 0, gl.RGBA, gl.UNSIGNED_BYTE, img);
    });
    var bufs = [gl.createBuffer(), gl.createBuffer()];
    var buf = bufs[0], buf2 = bufs[1];
    gl.bindBuffer(gl.ARRAY_BUFFER, buf);
    var bufArr = new Float32Array(bufData);
    time("bufferDataNoChange", function() {
        for (var i=0; i<100; i++)
            gl.bufferData(gl.ARRAY_BUFFER, bufArr, gl.STATIC_DRAW);
    });
    time("bufferSubDataNoChange", function() {
        for (var i=0; i<100; i++)
            gl.bufferSubData(gl.ARRAY_BUFFER, 0, bufArr);
    });
    time("bufferData", function() {
        var bufArr = new Float32Array(bufData);
        for (var i=0; i<25; i++)
            gl.bufferData(gl.ARRAY_BUFFER, bufArr, gl.STATIC_DRAW);
    });
    time("bufferSubData", function() {
        var bufArr = new Float32Array(bufData);
        for (var i=0; i<25; i++)
            gl.bufferSubData(gl.ARRAY_BUFFER, 0, bufArr);
    });
    var sh = new Shader(gl, 'vert-v', 'frag-v');
    gl.disable(gl.DEPTH_TEST);
    sh.use();
    var v = sh.attrib('Vertex');
    for (var i=0; i<16; i++)
        gl.disableVertexAttribArray(i);
    gl.enableVertexAttribArray(v);
    gl.vertexAttribPointer(v, 4, gl.FLOAT, false, 0, 0);
    time("verticeDraw", function() {
        for (var i=0; i<100; i++)
            gl.drawArrays(gl.TRIANGLES, 0, 256*256);
        gl.readPixels(0,0,1,1,gl.RGBA, gl.UNSIGNED_BYTE);
    });
    gl.bindBuffer(gl.ARRAY_BUFFER, buf2);
    gl.bufferData(gl.ARRAY_BUFFER, bufArr, gl.STATIC_DRAW);
    time("verticeDrawC", function() {
        for (var i=0; i<100; i++) {
            gl.bindBuffer(gl.ARRAY_BUFFER, (i % 2 == 0) ? buf : buf2);
            gl.drawArrays(gl.TRIANGLES, 0, 256*256);
        }
        gl.readPixels(0,0,1,1,gl.RGBA, gl.UNSIGNED_BYTE);
    });
    // Drawing arrays with vertexAttribPointer seems to have been removed from WebGL.
/*    gl.bindBuffer(gl.ARRAY_BUFFER, null);
    gl.vertexAttribPointer(v, 4, gl.FLOAT, false, 0, bufArr);
    time("verticeDrawVA", function() {
        for (var i=0; i<100; i++)
            gl.drawArrays(gl.TRIANGLES, 0, 256*256);
        gl.readPixels(0,0,1,1,gl.RGBA, gl.UNSIGNED_BYTE);
    });
    time("verticeDrawVAC", function() {
        for (var i=0; i<100; i++) {
            gl.vertexAttribPointer(v, 4, gl.FLOAT, false, 0, bufArr);
            gl.drawArrays(gl.TRIANGLES, 0, 256*256);
        }
        gl.readPixels(0,0,1,1,gl.RGBA, gl.UNSIGNED_BYTE);
    });*/
    sh.destroy();
    sh = new Filter(gl, 'vert-t', 'frag-t');
    sh.apply();
    time("textureDraw", function() {
        for (var i=0; i<1000; i++)
            gl.drawArrays(gl.TRIANGLES, 0, 6);
        gl.readPixels(0,0,1,1,gl.RGBA, gl.UNSIGNED_BYTE);
    });
    sh.destroy();
    time("readPixels", function() {
        for (var i=0; i<100; i++)
            gl.readPixels(0, 0, 256, 256, gl.RGBA, gl.UNSIGNED_BYTE);
    });
    time("getImageData", function() {
        for (var i=0; i<100; i++)
            gl.getImageData(0, 0, 256, 256);
    });
    gl.bindTexture(gl.TEXTURE_2D, null);
    gl.bindBuffer(gl.ARRAY_BUFFER, null);
    bufs.forEach(function(buf){ gl.deleteBuffer(buf) });
    gl.deleteTexture(tex);
}


Tests.endUnit = function(gl) {
}

</script>
<script id="vert-v" type="x-shader/x-vertex">

  attribute vec4 Vertex;
  void main()
  {
    gl_Position = Vertex;
  }
</script>
<script id="frag-v" type="x-shader/x-fragment">

  precision mediump float;

  void main()
  {
    gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);
  }
</script>
<script id="vert-t" type="x-shader/x-vertex">


  attribute vec3 Vertex;
  attribute vec2 Tex;
  varying vec2 texCoord0;
  void main()
  {
    gl_Position = vec4(Vertex, 1.0);
    texCoord0 = Tex;
  }
</script>
<script id="frag-t" type="x-shader/x-fragment">

  precision mediump float;

  uniform sampler2D Texture;

  varying vec2 texCoord0;
  void main()
  {
    gl_FragColor = texture2D(Texture, texCoord0);
  }
</script>

<style>canvas{ position:absolute; }
img{ display:none; }</style>
</head><body>
<h3>100x 256x256x4 texture upload with texImage2D (26.2MB total)</h3>
<p id="texImage2D"></p>
<h3>100x 256x256x4 texture upload with texSubImage2D (26.2MB total)</h3>
<p id="texSubImage2D"></p>
<h3>100x 256x256x4 texture upload with texImage2DHTML (26.2MB total)</h3>
<p id="texImage2DHTML"></p>
<h3>100x 256x256x4 texture upload with texSubImage2DHTML (26.2MB total)</h3>
<p id="texSubImage2DHTML"></p>
<h3>100x 256x256x4 readPixels (26.2MB total)</h3>
<p id="readPixels"></p>
<h3>100x 256x256x4 getImageData (26.2MB total)</h3>
<p id="getImageData"></p>
<h3>25x 256x256x4 float bufferData (6.6MB total)</h3>
<p id="bufferData"></p>
<h3>25x 256x256x4 float bufferSubData (6.6MB total)</h3>
<p id="bufferSubData"></p>
<h3>100x 256x256x4 float bufferData, reuse Float32Array (26.2MB total)</h3>
<p id="bufferDataNoChange"></p>
<h3>100x 256x256x4 float bufferSubData, reuse Float32Array (26.2MB total)</h3>
<p id="bufferSubDataNoChange"></p>
<h3>100x 256x256 vert VBO draw</h3>
<p id="verticeDraw"></p>
<h3>100x 256x256 vert VBO draw, change VBO after each draw</h3>
<p id="verticeDrawC"></p>
<!--<h3>100x 256x256 vert vertex array draw</h3>
<p id="verticeDrawVA"></p>
<h3>100x 256x256 vert vertex array draw, change array after each draw</h3>
<p id="verticeDrawVAC"></p>-->
<h3>1000x 256x256 texture draw</h3>
<p id="textureDraw"></p>
<canvas id="gl" width="256" height="256"></canvas>
<img id="logo" src="" width="256" height="256">
</body></html>
